package com.ollobot.authorization.config;

import org.springframework.boot.actuate.info.InfoContributor;
import org.springframework.boot.actuate.info.Info;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.boot.actuate.health.HealthIndicator;
import org.springframework.boot.actuate.health.Health;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.mail.javamail.JavaMailSender;

import javax.sql.DataSource;
import java.sql.Connection;
import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.Map;

@Configuration
public class ActuatorConfig {

    @Autowired
    private DataSource dataSource;

    @Autowired
    private RedisTemplate<String, Object> redisTemplate;

    @Autowired
    private JavaMailSender mailSender;

    /**
     * 自定义应用信息贡献者
     */
    @Bean
    public InfoContributor customInfoContributor() {
        return builder -> {
            Map<String, Object> appInfo = new HashMap<>();
            appInfo.put("name", "OlloBot Authorization Server");
            appInfo.put("description", "Unified authorization server supporting Apple, Google, Facebook and email verification login");
            appInfo.put("version", "1.0.0");
            appInfo.put("build-time", LocalDateTime.now().toString());
            appInfo.put("features", new String[]{
                "OAuth2 Authorization Server",
                "Multi-provider OAuth2 Login (Google, Facebook, Apple)",
                "Email Verification",
                "JWT Token Management",
                "Redis Session Management",
                "MySQL Database Integration"
            });
            
            builder.withDetail("application", appInfo);
        };
    }

    /**
     * 自定义数据库健康检查
     */
    @Bean
    public HealthIndicator databaseHealthIndicator() {
        return () -> {
            try (Connection connection = dataSource.getConnection()) {
                if (connection.isValid(1)) {
                    return Health.up()
                        .withDetail("database", "MySQL")
                        .withDetail("status", "Connected")
                        .withDetail("url", connection.getMetaData().getURL())
                        .build();
                } else {
                    return Health.down()
                        .withDetail("database", "MySQL")
                        .withDetail("status", "Connection invalid")
                        .build();
                }
            } catch (Exception e) {
                return Health.down()
                    .withDetail("database", "MySQL")
                    .withDetail("status", "Connection failed")
                    .withDetail("error", e.getMessage())
                    .build();
            }
        };
    }

    /**
     * 自定义Redis健康检查
     */
    @Bean
    public HealthIndicator redisHealthIndicator() {
        return () -> {
            try {
                String pong = redisTemplate.getConnectionFactory().getConnection().ping();
                if ("PONG".equals(pong)) {
                    return Health.up()
                        .withDetail("redis", "Connected")
                        .withDetail("response", pong)
                        .build();
                } else {
                    return Health.down()
                        .withDetail("redis", "Unexpected response")
                        .withDetail("response", pong)
                        .build();
                }
            } catch (Exception e) {
                return Health.down()
                    .withDetail("redis", "Connection failed")
                    .withDetail("error", e.getMessage())
                    .build();
            }
        };
    }

    /**
     * 自定义邮件服务健康检查
     */
    @Bean
    public HealthIndicator mailHealthIndicator() {
        return () -> {
            try {
                // 简单的连接测试
                mailSender.createMimeMessage();
                return Health.up()
                    .withDetail("mail", "Mail service available")
                    .withDetail("provider", "163.com")
                    .build();
            } catch (Exception e) {
                return Health.down()
                    .withDetail("mail", "Mail service unavailable")
                    .withDetail("error", e.getMessage())
                    .build();
            }
        };
    }

    /**
     * 自定义OAuth2服务健康检查
     */
    @Bean
    public HealthIndicator oauth2HealthIndicator() {
        return () -> {
            try {
                // 检查OAuth2配置是否正确加载
                Map<String, Object> details = new HashMap<>();
                details.put("google", "Configured");
                details.put("facebook", "Configured");
                details.put("apple", "Configured");
                
                return Health.up()
                    .withDetail("oauth2-providers", details)
                    .withDetail("status", "OAuth2 providers configured")
                    .build();
            } catch (Exception e) {
                return Health.down()
                    .withDetail("oauth2", "Configuration error")
                    .withDetail("error", e.getMessage())
                    .build();
            }
        };
    }
}
